package br.unifor.cct.mia.velocity;

import br.unifor.cct.mia.evolutionary.Particula;
import br.unifor.cct.mia.pso.PSO;

public class PSOBasicVelocity implements Velocity {

	public Object execute(Object o) {
		Object[] value = (Object[])o;
		PSO pso = (PSO)value[0];
		
		for(Particula particula:pso.getPopulacao()) {			
			for( int i=0; i<particula.getPosition().length; i++ ) {
				double v = particula.getVelocity()[i];
				double p = particula.getPosition()[i];
				double pB = particula.getBestPosition()[i];				
				double gB = ((Particula)pso.getBestIndividual()).getPosition()[i];
				
				double vel = v + PSO.C1*( pB-p ) + PSO.C2*( gB-p );
				
				if((vel > PSO.MAX_VEL) || (vel < PSO.MIN_VEL))
					vel = (PSO.MAX_VEL < vel)?PSO.MAX_VEL:PSO.MIN_VEL;
				
				particula.getVelocity()[i] = vel;		
				
				
				particula.getPosition()[i] += vel;
				if ( particula.getPosition()[i] > pso.getMaxVal() ) {
					particula.getPosition()[i] = pso.getMaxVal();
				}
				else if ( particula.getPosition()[i] < pso.getMinVal() ) {
					particula.getPosition()[i] = pso.getMinVal();
				}				
			}			
		}
		
		return null;
	}
	
	public static double randDoubleValue(double min, double max) {
		return (min + Math.random() * (max - min));
	}
	
	public double sigmoid(double v) {
		double result = 0;
		
		result = 1 / (1+ Math.pow(Math.E,-v));
		
		return result;
	}
	
	public static void main(String[] args) {
		System.out.println(new PSOBasicVelocity().sigmoid(-6));
		System.out.println(new PSOBasicVelocity().sigmoid(0));
		System.out.println(new PSOBasicVelocity().sigmoid(6));
	}
	
}
